package com.dnake;

import android.annotation.SuppressLint;
import android.app.Activity;
import android.app.ActivityManager;
import android.app.Application;
import android.content.Context;
import android.database.sqlite.SQLiteDatabase;
import android.net.Uri;
import android.support.multidex.MultiDex;
import android.util.Log;

import com.alibaba.sdk.android.oss.ClientConfiguration;
import com.alibaba.sdk.android.oss.OSS;
import com.alibaba.sdk.android.oss.OSSClient;
import com.alibaba.sdk.android.oss.common.OSSLog;
import com.alibaba.sdk.android.oss.common.auth.OSSCredentialProvider;
import com.alibaba.sdk.android.oss.common.auth.OSSPlainTextAKSKCredentialProvider;
import com.baidu.aip.face.AipFace;
import com.dnake.db.DaoMaster;
import com.dnake.db.DaoSession;
import com.dnake.entity.EventBusVoipBean;
import com.dnake.handle.UnCeHandler;
import com.dnake.panel.BuildConfig;
import com.dnake.utils.FaceDB;
import com.dnake.utils.VoipUtils;
import com.hyphenate.EMMessageListener;
import com.hyphenate.chat.EMClient;
import com.hyphenate.chat.EMMessage;
import com.hyphenate.chat.EMOptions;
import com.orhanobut.logger.AndroidLogAdapter;
import com.orhanobut.logger.Logger;
import com.wx.android.common.util.SharedPreferencesUtils;
import com.yuntongxun.ecsdk.ECDevice;
import com.yuntongxun.ecsdk.ECVoIPCallManager;
import com.yuntongxun.ecsdk.VideoRatio;
import com.yuntongxun.ecsdk.VoipMediaChangedInfo;

import org.greenrobot.eventbus.EventBus;
import org.xutils.x;

import java.util.ArrayList;
import java.util.List;
import java.util.concurrent.TimeUnit;

import io.reactivex.Observable;
import io.reactivex.functions.Consumer;
import io.reactivex.schedulers.Schedulers;
import me.yokeyword.fragmentation.Fragmentation;

/**
 * @author haoyuliu
 * @since 2017/6/26
 */
public class WeKerApplication extends Application {
    private static WeKerApplication instances;
    private DaoMaster.DevOpenHelper mHelper;
    private SQLiteDatabase db;
    private DaoMaster mDaoMaster;
    private DaoSession mDaoSession;
    private EMMessageListener messageListener;
    public static   AipFace client;
    ArrayList<Activity> list = new ArrayList<Activity>();
    public FaceDB mFaceDB;
    private OSS oss;
    @SuppressLint("CheckResult")
    @Override
    public void onCreate() {
        super.onCreate();
        MultiDex.install(this);
        Logger.addLogAdapter(new AndroidLogAdapter(){
            @Override
            public boolean isLoggable(int priority, String tag) {
                return true;
            }
        });

        mFaceDB = new FaceDB(this.getExternalCacheDir().getPath());
        instances = this;

        EMOptions options = new EMOptions();
        // 默认添加好友时，是不需要验证的，改成需要验证
        options.setAcceptInvitationAlways(false);
        options.setRequireAck(true);
        options.setRequireDeliveryAck(false);
        options.setAutoLogin(true);
        //初始化环信
        EMClient.getInstance().init(this, options);
        EMClient.getInstance().callManager().getCallOptions().setIsSendPushIfOffline(true);
        registerMessageListener();


        //初始化xUtils
        x.Ext.init(this);
        x.Ext.setDebug(BuildConfig.DEBUG); // 是否输出debug日志, 开启debug会影响性能.
        //配置数据库
        setDatabase();
        Fragmentation.builder().debug(BuildConfig.DEBUG)
                .install();

        //设置该CrashHandler为程序的默认处理器
        UnCeHandler catchExcep = new UnCeHandler(this);
        Thread.setDefaultUncaughtExceptionHandler(catchExcep);
        initFace();
        initRl();
        Observable.timer(500, TimeUnit.MILLISECONDS)
                .observeOn(Schedulers.newThread())
                .subscribe(new Consumer<Long>() {
                    @Override
                    public void accept(Long aLong) throws Exception {
                        initOSS(Constant.OSS_ENDPOINT);
                    }
                });
    }

    /**
     * 初始化OSS
     * @param endpoint
     */
    public void initOSS(String endpoint) {
        OSSCredentialProvider credentialProvider;
        credentialProvider = new OSSPlainTextAKSKCredentialProvider(Constant.OSS_ACCESS_KEY_ID,Constant.OSS_ACCESS_KEY_SECRET);
        ClientConfiguration conf = new ClientConfiguration();
        conf.setConnectionTimeout(15 * 1000); // 连接超时，默认15秒
        conf.setSocketTimeout(15 * 1000); // socket超时，默认15秒
        conf.setMaxConcurrentRequest(5); // 最大并发请求书，默认5个
        conf.setMaxErrorRetry(2); // 失败后最大重试次数，默认2次
        oss = new OSSClient(getApplicationContext(), endpoint, credentialProvider, conf);
        OSSLog.enableLog();

    }

    public OSS getOss() {
        return oss;
    }

    /**
     * 初始化容联
     */
    private void initRl(){
        if(!ECDevice.isInitialized()&&isMainProcess()) {
            ECDevice.initial(getApplicationContext(), new ECDevice.InitListener() {
                @Override
                public void onInitialized() {
                    callBack();
                }
                @Override
                public void onError(Exception e) {

                }
            });
        }
    }


    /**
     * 获取当前进程名
     */
    private String getCurrentProcessName() {
        int pid = android.os.Process.myPid();
        String processName = "";
        ActivityManager manager = (ActivityManager) getApplicationContext().getSystemService(Context.ACTIVITY_SERVICE);
        for (ActivityManager.RunningAppProcessInfo process : manager.getRunningAppProcesses()) {
            if (process.pid == pid) {
                processName = process.processName;
            }
        }
        return processName;
    }

    /**
     * 包名判断是否为主进程
     *
     * @param
     * @return
     */
    public boolean isMainProcess() {
        return getApplicationContext().getPackageName().equals(getCurrentProcessName());
    }
    /**
     * VoIP通话状态监听，使用VoIP通话功能的开发者需要设置。
     */
    private void callBack(){
        // VoIP通话状态监听，使用VoIP通话功能的开发者需要设置。
        ECVoIPCallManager callInterface = ECDevice.getECVoIPCallManager();
        if(callInterface != null) {
            callInterface.setOnVoIPCallListener(new ECVoIPCallManager.OnVoIPListener() {
                @Override
                public void onVideoRatioChanged(VideoRatio videoRatio) {

                }

                @Override
                public void onSwitchCallMediaTypeRequest(String s, ECVoIPCallManager.CallType callType) {

                }

                @Override
                public void onSwitchCallMediaTypeResponse(String s, ECVoIPCallManager.CallType callType) {

                }

                @Override
                public void onDtmfReceived(String s, char c) {
                    Log.e("111", "onDtmfReceived: "+c );
                    EventBus.getDefault().post(new EventBusVoipBean(Constant.EVENTBUS_VOIP_DTMF,c+"",null));
                }

                @Override
                public void onCallEvents(ECVoIPCallManager.VoIPCall voipCall) {
                    // 处理呼叫事件回调
                    if(voipCall == null) {
                        Log.e("SDKCoreHelper", "handle call event error , voipCall null");
                        return ;
                    }
                    EventBus.getDefault().post(new EventBusVoipBean(Constant.EVENTBUS_VOIP_STATE,"",voipCall));
                }

                @Override
                public void onMediaDestinationChanged(VoipMediaChangedInfo voipMediaChangedInfo) {

                }
            });
        }
    }
    /**
     * 初始化百度人脸
     */
    private void initFace() {
        // 初始化一个FaceClient
        client = new AipFace(BuildConfig.APP_ID, BuildConfig.API_KEY, BuildConfig.SECRET_KEY);
        // 可选：设置网络连接参数
        client.setConnectionTimeoutInMillis(5000);
        //超时设置为5秒
        client.setSocketTimeoutInMillis(6000);
    }
    public static WeKerApplication getContext() {
        return instances;
    }

    /**
     * 向Activity列表中添加Activity对象*/
    public void addActivity(Activity a){
        list.add(a);
    }

    /**
     * Activity关闭时，删除Activity列表中的Activity对象*/
    public void removeActivity(Activity a){
        list.remove(a);
    }


    /**
     * 关闭Activity列表中的所有Activity*/
    public void finishActivity(){
        for (Activity activity : list) {
            if (null != activity) {
                activity.finish();
            }
        }
        //杀死该应用进程
        EMClient.getInstance().chatManager().removeMessageListener(messageListener);
        android.os.Process.killProcess(android.os.Process.myPid());
    }


    /**
     * 设置greenDao
     */
    private void setDatabase() {
        // 通过 DaoMaster 的内部类 DevOpenHelper，你可以得到一个便利的 SQLiteOpenHelper 对象。
        // 可能你已经注意到了，你并不需要去编写「CREATE TABLE」这样的 SQL 语句，因为 greenDAO 已经帮你做了。
        // 注意：默认的 DaoMaster.DevOpenHelper 会在数据库升级时，删除所有的表，意味着这将导致数据的丢失。
        // 所以，在正式的项目中，你还应该做一层封装，来实现数据库的安全升级。
        mHelper = new DaoMaster.DevOpenHelper(this, "notes-db", null);
        db = mHelper.getWritableDatabase();
        // 注意：该数据库连接属于 DaoMaster，所以多个 Session 指的是相同的数据库连接。
        mDaoMaster = new DaoMaster(db);
        mDaoSession = mDaoMaster.newSession();
    }

    public DaoSession getDaoSession() {
        return mDaoSession;
    }
    public SQLiteDatabase getDb() {
        return db;
    }

    /**
     * Global listener
     * If this event already handled by an activity, you don't need handle it again
     * activityList.size() <= 0 means all activities already in background or not in Activity Stack
     */
    protected void registerMessageListener() {
        messageListener = new EMMessageListener() {

            @Override
            public void onMessageReceived(List<EMMessage> messages) {
            }

            @Override
            public void onCmdMessageReceived(List<EMMessage> messages) {
                for (EMMessage message : messages) {
                    //取第一个消息
                    EventBus.getDefault().post(message);
                    break;
                }
            }

            @Override
            public void onMessageRead(List<EMMessage> messages) {
            }

            @Override
            public void onMessageDelivered(List<EMMessage> message) {
            }

            @Override
            public void onMessageChanged(EMMessage message, Object change) {

            }
        };
        EMClient.getInstance().chatManager().addMessageListener(messageListener);
    }

    @Override
    public void onTerminate() {
        super.onTerminate();
        EMClient.getInstance().chatManager().removeMessageListener(messageListener);
    }
}
